package com.liyu.net;

import com.liyu.controller.RequestProcessor;
import org.jetbrains.annotations.Contract;
import org.jetbrains.annotations.NotNull;

import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.LinkedBlockingDeque;
import java.util.concurrent.ThreadFactory;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicInteger;

/**
 * ????????????
 *
 * @author Yuhaotian
 * @date. 2022/10/31 14:37
 */
public class MainServer {
    /**
     * 端口号
     */
    private static final int PORT = 9999;
    /**
     * 自定义ThreadFactory
     **/
    private static final ThreadFactory NAMED_FACTORY = nameThreadFactory();
    /**
     * 连接客户端数量
     */
    public static int count = 0;
    /**
     * 连接对象
     */
    static List<Socket> user_list = new ArrayList<>();
    private static boolean running = true;

    /**
     * ToDo: 自定义线程名
     *
     * @return {@link ThreadFactory}
     * @author Yuhaotian
     * @date. 2022/10/28 17:43
     */
    @Contract(pure = true)
    private static @NotNull ThreadFactory nameThreadFactory() {
        AtomicInteger tag = new AtomicInteger(1);
        return (Runnable r) -> {
            Thread thread = new Thread(r);
            thread.setName("线程-" + tag.getAndIncrement());
            return thread;
        };
    }

    public static void main(String[] args) {
        // 启动服务器
        MainServer server = new MainServer();
        server.startServer();
    }

    /**
     * ToDo: 启动服务器
     *
     * @author Yuhaotian
     * @date. 2022/10/29 14:40
     */
    public void startServer() {
        try {
            DataBuffer.serverSocket = new ServerSocket(PORT);
            System.out.println("监听端口为" + PORT);
            // 创建线程池
            ThreadPoolExecutor threadPool = new ThreadPoolExecutor(10, 15, 60000,
                    TimeUnit.SECONDS, new LinkedBlockingDeque<>(), NAMED_FACTORY);
            while (running) {
                // 监听客户端连接
                Socket client = DataBuffer.serverSocket.accept();
                // 添加客户端
                user_list.add(client);
                // 输出客户端端口
                System.out.println("客户端连接：" + user_list.get(count).getPort());
                count++;// 客户端数加一
                //exec.execute(new s_talk(client));//????s_talk????
                threadPool.submit(new RequestProcessor(client));
            }
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }
}
